/**
 * @description: koa服务器，作为devServer
 */

const Koa = require('koa')
const fs = require('fs')
const path = require('path')
const {
  logger,
  getFileContent,
  getResContent,
  rewriteImport,
  isPkg,
  resolvePkgFile,
} = require('./server-utils')
const { createWebSocketServer } = require('./hrm/ws')
const chokidar = require('chokidar')

const app = new Koa()

app.use(async (ctx) => {
  const { url, query = {} } = ctx.request
  const pathname = url.split('?')[0]
  const fileFullPath = path.join(process.cwd(), pathname)

  // logger(
  //   'request: ',
  //   `\n url: ${pathname} \n query: ${JSON.stringify({ ...query })} \\n`,
  //   'info',
  // )
  if (pathname === '/' || pathname === '/index.html') {
    const content = getFileContent(path.join(process.cwd(), 'index.html'))
    ctx.type = 'text/html'

    // 1. 插入热更新的代码
    // 2. 这里的 replace 是 vue 中会使用 process.env
    ctx.body = content.replace(
      '<body>',
      `<body>
                  <script type="module" src="./server/hrm/client.js"></script>
                  <script> window.process = { env: { NODE_ENV: 'dev' } } </script>`,
    )
  } else if (pathname.endsWith('.ico')) {
    ctx.type = 'image/svg+xml'
    ctx.body = fs.readFileSync('./static/logo.svg')
  } else {
    const filePath = isPkg(pathname) ? resolvePkgFile(pathname) : fileFullPath
    const result = await getResContent(filePath, pathname, query)
    let code = result.code || `console.error("no code， ${pathname}")`

    code = !result.needRewriteImport ? code : await rewriteImport(fileFullPath, code)
    ctx.type = result.type
    ctx.body = code
  }
})

const port = 3000
function watchFiles() {
  const ws = createWebSocketServer({ port: port + 1 })
  const projectPath = 'src/'
  chokidar.watch(projectPath).on('change', (relativePath) => {
    logger('watch file', relativePath, 'info')
    ws.send({ file: relativePath })
  })
}
app.listen(port, () => {
  logger('server at: ', `http://localhost:${port}`, 'info')
  watchFiles()
})
